package com.xywl.escort.view.user.register

import android.os.Build
import android.os.Bundle
import android.os.CountDownTimer
import android.text.TextUtils
import com.alibaba.android.arouter.facade.annotation.Route
import com.alibaba.android.arouter.launcher.ARouter
import com.bumptech.glide.load.engine.DiskCacheStrategy
import com.trello.rxlifecycle2.LifecycleTransformer
import com.xywl.escort.R
import com.xywl.escort.base.BaseActivity
import com.xywl.escort.bean.BaseResp
import com.xywl.escort.bean.CaptchaBean
import com.xywl.escort.bean.GetSmsCodeReq
import com.xywl.escort.bean.RegisterReq
import com.xywl.escort.common.Constant
import com.xywl.escort.utils.*
import com.xywl.escort.widget.GlideApp
import dagger.android.AndroidInjection
import kotlinx.android.synthetic.main.activity_register.*
import timber.log.Timber
import java.util.regex.Pattern
import javax.inject.Inject

@Route(path = "/xy/register")
class RegisterActivity : BaseActivity(), RegisterContract.View {
    private var isCountDown: Boolean = false
    @Inject
    lateinit var mPresenter: RegisterContract.Presenter
    private var captchaKey = ""

    override fun onCreate(savedInstanceState: Bundle?) {
        AndroidInjection.inject(this)
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_register)

        showBackButton()
        setTitleText(R.string.user_register)

        text_register_agreement.setOnClickListener {
            ARouter.getInstance().build("/xy/web/links")
                    .withString("title", getString(R.string.user_register_agreement))
                    .withString("url", "file:///android_asset/register_agreement.html")
                    .navigation()
        }

        mPresenter.takeView(this)
        mPresenter.getCaptcha()
        text_send_ver_code.setOnClickListener {
            getSmsCode()
        }

        btn_confirm.setOnClickListener {
            register()
        }

        text_send_img_code.setOnClickListener {
            mPresenter.getCaptcha()
        }
    }

    private fun getSmsCode() {
        val phone = edit_phone.text.toString().trim()
        val imgCode = edit_msg_img_code.text.toString().trim()
        if (!NetworkUtil.isAvailable(this)) {
            ToastUtil.showTip(this, R.string.network_error)
            return
        }
        if (!RegexUtils.checkMobile(phone)) {
            ToastUtil.showTip(this, R.string.user_error_hint_phone)
            return
        }
        if (!isCountDown && checkCaptchaCode(imgCode)) {
            val req = GetSmsCodeReq()
            req.phone = phone
            req.operateType = 4
            req.captchaCode = imgCode
            req.captchaKey = captchaKey
            mPresenter.getCode(req)
        }
    }

    private var mVerificationTimer = object : CountDownTimer((60 * 1000).toLong(), 1000) {
        override fun onTick(millisUntilFinished: Long) {
            text_send_ver_code.isEnabled = false
            text_send_ver_code.text = getString(R.string.account_auth_cd_format, millisUntilFinished / 1000)
        }

        override fun onFinish() {
            text_send_ver_code.isEnabled = true
            text_send_ver_code.text = getString(R.string.account_auth_re_get)
            isCountDown = false
        }
    }

    private fun register() {
        val isChecked = checkbox.isChecked
        val account = edit_phone.text.toString().trim()
        val pwd = edit_pwd.text.toString().trim()
        val code = edit_msg_ver_code.text.toString().trim()
        val imgCode = edit_msg_img_code.text.toString().trim()
        val invitationCode = edit_invite_code.text.toString().trim()
        if (!NetworkUtil.isAvailable(this)) {
            ToastUtil.showTip(this, R.string.network_error)
            return
        }
        if (!RegexUtils.checkMobile(account)) {
            ToastUtil.showTip(this, R.string.user_error_hint_phone)
            return
        }
        if (!isChecked) {
            ToastUtil.showTip(this, R.string.user_agree_register_agreement)
            return
        }
        if (checkAccount(account) && checkPwd(pwd) && checkCode(code, imgCode)) {
            val password = MD5.encrypt(pwd)
            val channelId = TelephonyUtil.getChannelId(applicationContext)
            val req = RegisterReq()
            req.account = account
            req.pwd = password
            req.smsCode = code.toInt()
            req.invitationCode = invitationCode
            req.channelId = channelId
            req.ipaddress = DeviceUtils.getIPAddress(true)
            req.macAdds = DeviceUtils.getMacAddress(this)
            req.deviceId = UUIDUtil.getDeviceId(this)
            req.phoneBrand = Build.BRAND
            req.phoneModel = Build.MODEL
            req.captchaCode = imgCode
            req.captchaKey = captchaKey
            Timber.e("req=$req")

            mPresenter.register(req)
        }
    }

    private fun checkPwd(pwd: String): Boolean {
        val regex = "^(?=.*[a-zA-Z])(?=.*[0-9])[0-9A-Za-z!@~#\$%^&*()-+_`~,./=?\\\\|]{8,20}\$"
        if (TextUtils.isEmpty(pwd)) {
            ToastUtil.showTip(this, R.string.user_account_hint_password)
            return false
        } else if (pwd.length < Constant.Length.MIN_LOGIN_PWD_LENGTH) {
            ToastUtil.showTip(this, R.string.user_account_reset_password_error)
            return false
        } else if (!Pattern.matches(regex, pwd)) {
            ToastUtil.showTip(this, R.string.user_password_format_error)
            return false
        }
        return true
    }

    private fun checkAccount(account: String): Boolean {
        if (TextUtils.isEmpty(account)) {
            ToastUtil.showTip(this, R.string.user_account_hint_account)
            return false
        }
        return true
    }

    private fun checkCaptchaCode(imgCode: String): Boolean {
        if (TextUtils.isEmpty(imgCode)) {
            ToastUtil.showTip(this, R.string.user_img_code_empty)
            return false
        }
        return true
    }

    private fun checkCode(smsCode: String, imgCode: String): Boolean {
        if (TextUtils.isEmpty(smsCode)) {
            ToastUtil.showTip(this, R.string.user_sms_code_empty)
            return false
        }
        if (TextUtils.isEmpty(imgCode)) {
            ToastUtil.showTip(this, R.string.user_img_code_empty)
            return false
        }
        return true
    }

    override fun isActive(): Boolean {
        return false
    }

    override fun <T> bindToLife(): LifecycleTransformer<T> {
        return this.bindToLifecycle()
    }

    override fun startCountDown() {
        isCountDown = true
        text_send_ver_code.isEnabled = false
        mVerificationTimer.start()
    }

    override fun getCodeFailure(msg: String?) {
        Timber.tag("RegisterActivity").e("msg=$msg")
        if (!TextUtils.isEmpty(msg)) {
            ToastUtil.showTip(this, msg)
        }
    }

    override fun getCaptchaSuccess(bean: CaptchaBean?) {
        Timber.e("getCaptchaSuccess")
        if (null != bean) {
            val bitmap = bean.bitmap
            captchaKey = bean.captchaKey
            GlideApp.with(this)
                    .load(bitmap)
                    .centerCrop()
                    .diskCacheStrategy(DiskCacheStrategy.NONE)
                    .skipMemoryCache(true)
                    .placeholder(R.mipmap.icon_default_picture)
                    .into(img_code)
        }
    }

    override fun getCaptchaFailure() {
        Timber.e("getCaptchaFailure")
    }

    override fun registerSuccess(resp: BaseResp?) {
        ToastUtil.showTip(this, R.string.user_register_success)
        finish()
    }

    override fun registerFailure(msg: String?) {
        if (TextUtils.isEmpty(msg)) {
            ToastUtil.showTip(this, R.string.user_register_failure)
        } else {
            ToastUtil.showTip(this, msg)
        }
    }

    override fun onBackPressed() {
        super.onBackPressed()
        mVerificationTimer.onFinish()
        mVerificationTimer.cancel()
    }

    override fun onDestroy() {
        super.onDestroy()
        mPresenter.unSubscribe()
        mVerificationTimer.onFinish()
        mVerificationTimer.cancel()
    }
}
